<template>
  <div
    class="carousel-item-container"
    ref="container"
    @mousemove="handlerMouseMove"
    @mouseleave="handlerMouseLeave"
  >
    <div
      class="carousel-img"
      ref="image"
      :style="imagePosition"
    >
      <ImageLoader
        :src="carousel.bigImg"
        :placeholder="carousel.midImg"
        @load="this.showText"
      />
    </div>
    <div
      class="title"
      ref="title"
    >{{ carousel.title }}</div>
    <div
      class="desc"
      ref="desc"
    >{{ carousel.description }}</div>
  </div>
</template>

<script>
import ImageLoader from "@/components/ImageLoader";
export default {
  props: ["carousel"],
  components: {
    ImageLoader,
  },
  data() {
    return {
      titleWidth: 0,
      descWidth: 0,
      containerSize: null, // 外层容器尺寸
      innerSize: null, // 内存容器尺寸
      mouseX: 0,
      mouseY: 0,
    };
  },
  computed: {
    // 计算 图片的位置：跟随鼠标
    imagePosition() {
      // 容错处理
      if (!this.containerSize || !this.innerSize) return {};
      const extraWidth = this.innerSize.width - this.containerSize.width;
      const extraHeight = this.innerSize.height - this.containerSize.height;
      /**
       * 容器之间最大宽度差：container.width - inner.width
       * ==================对应===================== = k
       * 鼠标最大的距离：外层容器宽度 container.width
       *
       * 当前容器宽度差
       * ============ = k
       * 当前鼠标的距离
       *
       * diffWidth = 当前鼠标x距离 * k
       */
      const left = (-extraWidth / this.containerSize.width) * this.mouseX;
      const top = (-extraHeight / this.containerSize.height) * this.mouseY;
      return {
        transform: `translate(${left}px, ${top}px)`,
      };
    },
    center() {
      return {
        x: this.containerSize.width / 2,
        y: this.containerSize.height / 2,
      };
    },
  },
  mounted() {
    this.titleWidth = this.$refs.title.clientWidth;
    this.descWidth = this.$refs.desc.clientWidth;
    this.setSize();
    this.mouseX = this.center.x;
    this.mouseY = this.center.y;
    window.addEventListener("resize", this.setSize);
  },
  destroyed() {
    window.removeEventListener("resize", this.setSize);
  },
  methods: {
    // 展示轮播图中的文本：图片加载完成之后
    showText() {
      // 显示文本：透明度为1，宽度设置为0
      this.$refs.title.style.opacity = 1;
      this.$refs.title.style.width = 0;
      this.$refs.desc.style.opacity = 1;
      this.$refs.desc.style.width = 0;
      // 强制浏览器重新渲染：reflow
      this.$refs.title.clientWidth;
      // 修改元素宽度，设置过渡
      this.$refs.title.style.width = this.titleWidth + "px";
      this.$refs.title.style.transition = `1s`;
      this.$refs.desc.style.width = this.descWidth + "px";
      this.$refs.desc.style.transition = `2s 1s`;
    },
    // 保存容器尺寸大小数据
    setSize() {
      this.containerSize = {
        width: this.$refs.container.clientWidth,
        height: this.$refs.container.clientHeight,
      };

      this.innerSize = {
        width: this.$refs.image.clientWidth,
        height: this.$refs.image.clientHeight,
      };
    },
    // 鼠标移动
    handlerMouseMove(e) {
      // 获取 矩形信息
      const rect = this.$refs.container.getBoundingClientRect();
      this.mouseX = e.clientX - rect.left;
      this.mouseY = e.clientY - rect.top;
    },
    // 鼠标移出时，还原中间位置
    handlerMouseLeave() {
      this.mouseX = this.center.x;
      this.mouseY = this.center.y;
    },
  },
};
</script>

<style lang="less" scoped>
@import "~@/style/minix.less";
@import "~@/style/var.less";
.carousel-item-container {
  position: relative;
  overflow: hidden;
  width: 100%;
  height: 100%;
  color: #fff;
}
.carousel-img {
  position: absolute;
  left: 0;
  top: 0;
  width: 110%;
  height: 110%;
  transition: 0.3s;
}
.title,
.desc {
  position: absolute;
  left: 30px;
  letter-spacing: 3px;
  text-shadow: 1px 0 0 rgba(0, 0, 0, 0.5), -1px 0 0 rgba(0, 0, 0, 0.5),
    0 1px 0 rgba(0, 0, 0, 0.5), 0 -1px 0 rgba(0, 0, 0, 0.5);
  opacity: 0;
  white-space: nowrap;
  overflow: hidden;
}
.title {
  top: calc(50% - 40px);
  font-size: 2em;
}
.desc {
  top: calc(50% + 20px);
  font-size: 1.2em;
  color: lighten(@gray, 20%);
}
</style>